package com.imooc.mybatisplusappdemo.controller;


import cn.hutool.core.lang.UUID;
import cn.hutool.crypto.digest.MD5;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.core.mapper.BaseMapper;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.core.toolkit.StringUtils;
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import com.baomidou.mybatisplus.extension.api.R;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.imooc.mybatisplusappdemo.account.AccountQuery;
import com.imooc.mybatisplusappdemo.entity.Account;
import com.imooc.mybatisplusappdemo.entity.Customer;
import com.imooc.mybatisplusappdemo.entity.Role;
import com.imooc.mybatisplusappdemo.service.AccountService;
import com.imooc.mybatisplusappdemo.service.RoleService;
import com.imooc.mybatisplusappdemo.util.ResultUtil;
import java.util.List;
import java.util.Map;
import javax.servlet.http.HttpSession;
import lombok.val;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.ui.Model;
import org.springframework.web.bind.annotation.DeleteMapping;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.PutMapping;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;

import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.ResponseBody;

/**
 * <p>
 * 账号表 前端控制器
 * </p>
 *
 * @author sanchongmen
 * @since 2021-03-22
 */
@Controller
@RequestMapping("/account")
public class AccountController {

  @Autowired
  private AccountService accountService;

  @Autowired
  private RoleService roleService;

  /**
   * 进入列表页
   *
   * @return
   */
  @GetMapping("toList")
  public String toList() {
    return "account/accountList";
  }

  @GetMapping("list")
  @ResponseBody
  public R<Map<String, Object>> list(AccountQuery accountQuery) {

    QueryWrapper<Account> wrapper = Wrappers.<Account>query();
    wrapper.like(StringUtils.isNotBlank("realName"), "a.real_Name", accountQuery.getRealName())
        .like(StringUtils.isNotBlank("email"), "a.email", accountQuery.getEmail());

    String createTimeRange = accountQuery.getCreateTimeRange();
    if (StringUtils.isNotBlank(createTimeRange)) {
      String[] timeArray = createTimeRange.split(" - ");
      wrapper.ge("a.create_time", timeArray[0])
          .le("a.create_time", timeArray[1]);
    }

    //自定义mapper要加上逻辑删除标志
    wrapper.eq("a.deleted", "0")
        .orderByDesc("a.account_id");

    IPage<Account> page = accountService
        .accountPage(new Page<Account>(accountQuery.getPage(), accountQuery.getLimit()), wrapper);

    return ResultUtil.buildPageR(page);

  }

  @GetMapping("toAdd")
  public String toAdd(Model model) {
    List<Role> roles = roleService.list(Wrappers.<Role>lambdaQuery().orderByAsc(Role::getRoleId));
    model.addAttribute("roles", roles);
    return "account/accountAdd";
  }

  /**
   * 新增操作
   *
   * @param account
   * @return
   */
  @PostMapping
  @ResponseBody
  public R<Object> add(@RequestBody Account account) {

    SetPasswordAndSalt(account);

    return ResultUtil.buildR(accountService.save(account));
  }

  /**
   * 设置加密密码和加密盐
   *
   * @param account
   */
  private void SetPasswordAndSalt(Account account) {
    String password = account.getPassword();
    String salt = UUID.fastUUID().toString().replaceAll("-", "");
    MD5 md5 = new MD5(salt.getBytes());
    String digestHex = md5.digestHex(password);
    account.setPassword(digestHex);
    account.setSalt(salt);
  }

  @GetMapping("toUpdate/{id}")
  public String toUpdate(@PathVariable long id, Model model) {
    Account account = accountService.getById(id);
    model.addAttribute("account", account);

    List<Role> roles = roleService.list(Wrappers.<Role>lambdaQuery().orderByAsc(Role::getRoleId));
    model.addAttribute("roles", roles);

    return "account/accountUpdate";
  }

  /**
   * 新增操作
   *
   * @param account
   * @return
   */
  @PutMapping
  @ResponseBody
  public R<Object> update(@RequestBody Account account) {

    if (StringUtils.isNotBlank(account.getPassword())) {
      SetPasswordAndSalt(account);
    } else {
      // 以前调用时密码为空串导致更新的发生, 所以设置为Null,跳过更新即可
      account.setPassword(null);
    }

    return ResultUtil.buildR(accountService.save(account));
  }

  /**
   * 删除账号
   *
   * @param id
   * @return
   */
  @DeleteMapping("/{id}")
  @ResponseBody
  public R<Object> delete(@PathVariable long id, HttpSession session) {
    val account = (Account) session.getAttribute("account");

    if (null != account && account.getAccountId().equals(id)) {
      return R.failed("不能删除自己哦!");
    }

    return ResultUtil.buildR(accountService.removeById(id));
  }

  /**
   * 进入详情页
   *
   * @return
   */
  @GetMapping("toDetail/{id}")
  public String toDetail(@PathVariable long id, Model model) {
    Account account = accountService.getAccountById(id);
    model.addAttribute("account", account);

    return "account/accountDetail";
  }

  /**
   * 验证用户名是否重复
   *
   * @return
   */
  @GetMapping("checkUsername/{username}")
  public R<Object> checkUsername(@PathVariable String username) {
    Integer count = accountService.lambdaQuery().eq(Account::getUsername, username).count();

    return R.ok(count);
  }

}

